<script lang="ts" setup>
import type { GenericTableApi } from '#/api/lowcode/generic';

import { computed, onMounted, ref, nextTick, watch } from 'vue';
import { useRoute } from 'vue-router';

import { Page, useVbenModal } from '@vben/common-ui';
import { isEmpty, downloadFileFromBlob } from '@vben/utils';
import { IconifyIcon } from '@vben/icons';

import { message, Popover, Button, Dropdown, Menu, MenuItem, Card, List, ListItem, ListItemMeta, Collapse, CollapsePanel } from 'ant-design-vue';

import formCreate from '@form-create/ant-design-vue';

import { ACTION_ICON, TableAction, useVbenVxeGrid } from '#/adapter/vxe-table';
import {
  createTableData,
  deleteTableData,
  exportTableData,
  getTableData,
  getTableConfig,
  updateTableData,
  batchDeleteTableData,
  // Magic API 接口
  getTableDataMagic,
  createTableDataMagic,
  updateTableDataMagic,
  deleteTableDataMagic,
  batchDeleteTableDataMagic,
  exportTableDataMagic,
} from '#/api/lowcode/generic';

import GenericForm from './modules/form.vue';

// 导入字典相关工具函数
import { getDictOptions, getDictLabel, deleteDictCache } from '#/utils';

defineOptions({
  name: 'GenericTableManagement',
});

const route = useRoute();

// 从URL参数获取表信息
const tableName = computed(() => (route.query.tableName as string) || '');
const configId = computed(() => Number(route.query.configId) || 0);
const dataSourceId = computed(() => {
  // 检查多种可能的参数名
  const param = route.query.dataSourceId || route.query.dataSourceConfigId;
  if (param === undefined || param === null || param === '') {
    return 1; // 只有在参数不存在时才使用默认值
  }
  const id = Number(param);
  return isNaN(id) ? 1 : id; // 只有在转换失败时才使用默认值
});

// API选择开关
const useMagicApi = ref(true); // 默认使用Magic API

// 视图模式枚举和状态
enum ViewMode {
  TABLE = 'table',
  CARD = 'card',
  LIST = 'list'
}

// 视图模式状态管理
const viewMode = ref<ViewMode>(ViewMode.TABLE);
const tableData = ref<GenericTableApi.TableData[]>([]);

// 表格元数据
const tableMetadata = ref<GenericTableApi.TableMetadata>();

// 左侧搜索树数据（静态数据）
const searchTreeData = ref([
  {
    title: '全部数据',
    key: 'all',
    children: [
      {
        title: '最近添加',
        key: 'recent',
      },
      {
        title: '最近修改',
        key: 'modified',
      },
    ]
  },
  {
    title: '按状态筛选',
    key: 'status',
    children: [
      {
        title: '启用',
        key: 'enabled',
      },
      {
        title: '禁用',
        key: 'disabled',
      }
    ]
  }
]);

// 选中的树节点
const selectedKeys = ref<string[]>(['all']);

// 选中的行ID
const checkedIds = ref<(number | string)[]>([]);

// 表单弹窗和引用
const formModalRef = ref();
const [FormModal, formModalApi] = useVbenModal({
  connectedComponent: GenericForm,
  destroyOnClose: true,
});

// 加载表格元数据
async function loadTableMetadata() {
  if (!tableName.value) {
    message.error('缺少表名参数');
    return;
  }

  try {
    // 保存旧的元数据用于缓存清理
    const oldMetadata = tableMetadata.value;
    
    const response = await getTableConfig(tableName.value);
    
    if (!response) {
      message.error('接口返回数据为空');
      return;
    }

    const data = response.data || response;
    const columns = Array.isArray(data) ? data : (data.columns || []);
    
    // 如果字段信息发生变更，清理旧的字典缓存
    if (oldMetadata?.columns) {
      clearDictionaryCache(oldMetadata.columns);
      console.log('表配置重新加载，已清理旧字典缓存');
    }
    
    // 动态识别主键字段
    let primaryKey = 'id';
    const pkColumn = columns.find((col: any) => col.primaryKey || col.isPrimaryKey);
    if (pkColumn) {
      primaryKey = pkColumn.javaField || pkColumn.field || pkColumn.columnName || 'id';
    }
    
    tableMetadata.value = {
      tableName: data.tableName || tableName.value,
      displayName: data.tableComment || data.displayName || tableName.value,
      primaryKey,
      columns,
      table: {
        dataSourceConfigId: data.dataSourceConfigId || data.dataSourceId || dataSourceId.value,
        ...data
      }
    };


    document.title = tableMetadata.value.displayName || tableMetadata.value.tableName;
    
    // 预加载新的字典数据
    preloadDictionaries(columns);
    console.log('表配置已更新，字典数据已预加载', { 
      columns: columns.length, 
      dictFields: columns.filter(isDictField).length 
    });
    
    // 元数据加载完成后，重新生成列配置和搜索表单
    nextTick(() => {
      const newColumns = useGridColumns();
      
      // 更新表格列配置
      if (gridApi && gridApi.setGridOptions) {
        gridApi.setGridOptions({
          columns: newColumns
        });
        
        // 生成Popover搜索表单规则
        if (columns && columns.length > 0) {
          popoverSearchFormRules.value = generateCompactSearchFormRules(columns);
        }
        
        gridApi.query();
      }
    });
    
    // 如果有表单已经打开，主动通知重建
    nextTick(() => {
      if (formModalRef.value && typeof formModalRef.value.forceRefreshForm === 'function') {
        formModalRef.value.forceRefreshForm();
        console.log('表配置重载完成，通知表单重建');
      }
    });
    
  } catch (error) {
    console.error('获取表元数据失败:', error);
    message.error('获取表结构失败: ' + (error?.message || error?.msg || '未知错误'));
  }
}

// 刷新字段信息和表单
async function refreshFieldsAndForm() {
  console.log('手动刷新字段信息和表单');
  
  // 重新加载表元数据
  await loadTableMetadata();
  
  // 如果表单modal已打开，强制刷新表单
  if (formModalRef.value && typeof formModalRef.value.forceRefreshForm === 'function') {
    formModalRef.value.forceRefreshForm();
  }
  
  message.success('字段信息已刷新');
}

// ========== 字典相关工具函数 ==========

// 判断字段是否需要字典支持
function isDictField(column: any): boolean {
  const htmlType = column.htmlType || '';
  return ['select', 'radio', 'checkbox'].includes(htmlType) && !!column.dictType;
}

// 批量预加载字典数据
function preloadDictionaries(columns: any[]) {
  if (!columns) return;
  
  const dictTypes = columns
    .filter(isDictField)
    .map(col => col.dictType)
    .filter(Boolean);
  
  // 触发字典数据缓存加载
  dictTypes.forEach(dictType => {
    try {
      getDictOptions(dictType);
    } catch (error) {
      console.warn(`字典加载失败: ${dictType}`, error);
    }
  });
}

// 清理字典缓存
function clearDictionaryCache(columns: any[]) {
  if (!columns) return;
  
  const dictTypes = columns
    .filter(isDictField)
    .map(col => col.dictType)
    .filter(Boolean);
  
  // 清理特定字典类型的缓存
  dictTypes.forEach(dictType => {
    try {
      deleteDictCache(dictType);
    } catch (error) {
      console.warn(`字典缓存清理失败: ${dictType}`, error);
    }
  });
}

// 格式化字典值为显示标签
function formatDictValue(value: any, dictType: string): string {
  if (!dictType) {
    return String(value || '');
  }
  
  if (value === null || value === undefined || value === '') {
    return '';
  }
  
  try {
    const dictOptions = getDictOptions(dictType);
    if (!dictOptions || dictOptions.length === 0) {
      return String(value);
    }
    
    // 尝试多种类型匹配
    let matchedOption = null;
    
    // 1. 直接匹配（严格相等）
    matchedOption = dictOptions.find(opt => opt.value === value);
    
    // 2. 字符串转换后匹配
    if (!matchedOption) {
      const stringValue = String(value);
      matchedOption = dictOptions.find(opt => String(opt.value) === stringValue);
    }
    
    // 3. 数字转换后匹配
    if (!matchedOption && !isNaN(Number(value))) {
      const numberValue = Number(value);
      matchedOption = dictOptions.find(opt => Number(opt.value) === numberValue);
    }
    
    // 4. 布尔值转换后匹配
    if (!matchedOption && (value === true || value === false || value === 'true' || value === 'false' || value === 1 || value === 0)) {
      const boolValue = value === true || value === 'true' || value === 1;
      matchedOption = dictOptions.find(opt => {
        const optBool = opt.value === true || opt.value === 'true' || opt.value === 1 || opt.value === '1';
        return optBool === boolValue;
      });
    }
    
    return matchedOption ? matchedOption.label : String(value);
  } catch (error) {
    console.error(`字典标签获取错误: ${dictType}, value: ${value}`, error);
    return String(value);
  }
}

// 获取字典选项列表（用于表单）
function getDictSelectOptions(dictType: string) {
  if (!dictType) return [];
  
  try {
    return getDictOptions(dictType).map(option => ({
      label: option.label,
      value: option.value
    }));
  } catch (error) {
    console.warn(`字典选项获取失败: ${dictType}`, error);
    return [];
  }
}

// 动态生成列配置，基于工作的静态版本修改
function useGridColumns() {
  
  // 如果没有元数据，返回静态配置（确保能工作）
  if (!tableMetadata.value?.columns) {
    return [
      { type: 'checkbox', width: 50 },
      { field: 'id', title: '编号' },
      { field: 'student_id', title: '学生编号' },
      { field: 'name', title: '名字' },
      { field: 'score', title: '分数' },
      { field: 'create_time', title: '创建时间' },
      { field: 'deleted', title: '是否删除' },
      {
        title: '操作',
        width: 180,
        fixed: 'right',
        slots: { default: 'actions' },
      },
    ];
  }

  // 有元数据时，根据条件动态生成
  const columns = [{ type: 'checkbox', width: 50 }];
  
  tableMetadata.value.columns.forEach((column: any) => {
    // 根据代码生成配置中的"列表"字段来决定是否显示
    const shouldShow = column.listOperationResult === true;
    
    if (shouldShow) {
      const columnConfig: any = {
        field: column.javaField || column.field,
        title: column.title,
        width: column.width || 120,
      };

      // 根据字段类型添加格式化器
      if (isDictField(column)) {
        // 字典字段：显示字典标签而不是原始值
        columnConfig.formatter = ({ cellValue }: any) => {
          return formatDictValue(cellValue, column.dictType);
        };
      } else if (column.javaType === 'LocalDateTime' || column.jdbcType === 'DATETIME' || (column.javaField || column.field).includes('time')) {
        columnConfig.formatter = ({ cellValue }: any) => {
          if (!cellValue) return '';
          try {
            return new Date(cellValue).toLocaleString('zh-CN');
          } catch {
            return String(cellValue);
          }
        };
      } else if (column.javaType === 'Boolean' || column.jdbcType === 'BIT') {
        columnConfig.cellRender = {
          name: 'CellSwitch',
          props: {
            disabled: true, // 只显示不可修改
            checkedChildren: '是',
            unCheckedChildren: '否',
            size: 'small'
          }
        };
      }

      columns.push(columnConfig);
    }
  });

  columns.push({
    title: '操作',
    width: 180,
    fixed: 'right',
    slots: { default: 'actions' },
  });

  return columns;
}

// 生成动态列配置
function generateColumns() {
  const columns: any[] = [
    { type: 'checkbox', width: 50 },
  ];

  if (!tableMetadata.value?.columns) {
    return columns;
  }

  
  // 根据字段属性动态添加列
  tableMetadata.value.columns.forEach((column: any) => {
    // 根据代码生成配置中的"列表"字段来决定是否显示
    const shouldShow = column.listOperationResult === true;
    
    if (shouldShow) {
      const columnConfig: any = {
        field: column.javaField || column.field,
        title: column.title,
        width: column.width || 120,
      };

      columns.push(columnConfig);
    }
  });

  // 添加操作列 
  columns.push({
    title: '操作',
    width: 180,
    fixed: 'right',
    slots: { default: 'actions' },
  });

  return columns;
}


// 时间格式化工具函数
function formatDateTime(timestamp: any): string | null {
  if (!timestamp) return null;
  
  try {
    let date: Date;
    
    if (timestamp instanceof Date) {
      date = timestamp;
    } else if (typeof timestamp === 'number') {
      date = new Date(timestamp);
    } else if (typeof timestamp === 'string') {
      date = new Date(timestamp);
    } else {
      return null;
    }
    
    // 检查日期是否有效
    if (isNaN(date.getTime())) {
      return null;
    }
    
    // 格式化为 yyyy-MM-dd HH:mm:ss
    const year = date.getFullYear();
    const month = String(date.getMonth() + 1).padStart(2, '0');
    const day = String(date.getDate()).padStart(2, '0');
    const hours = String(date.getHours()).padStart(2, '0');
    const minutes = String(date.getMinutes()).padStart(2, '0');
    const seconds = String(date.getSeconds()).padStart(2, '0');
    
    return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
  } catch (error) {
    console.warn('时间格式化失败:', error);
    return null;
  }
}

// 日期格式化工具函数（仅日期）
function formatDate(timestamp: any): string | null {
  if (!timestamp) return null;
  
  try {
    let date: Date;
    
    if (timestamp instanceof Date) {
      date = timestamp;
    } else if (typeof timestamp === 'number') {
      date = new Date(timestamp);
    } else if (typeof timestamp === 'string') {
      date = new Date(timestamp);
    } else {
      return null;
    }
    
    // 检查日期是否有效
    if (isNaN(date.getTime())) {
      return null;
    }
    
    // 格式化为 yyyy-MM-dd
    const year = date.getFullYear();
    const month = String(date.getMonth() + 1).padStart(2, '0');
    const day = String(date.getDate()).padStart(2, '0');
    
    return `${year}-${month}-${day}`;
  } catch (error) {
    console.warn('日期格式化失败:', error);
    return null;
  }
}

// 处理表单数据中的时间字段格式转换
function processFormDataTimeFields(formData: any): any {
  if (!tableMetadata.value) return formData;
  
  const processedData = { ...formData };
  
  tableMetadata.value.columns.forEach(col => {
    const field = col.javaField || col.field || col.columnName;
    const javaType = col.javaType || '';
    const jdbcType = (col.jdbcType || col.columnType || '').toLowerCase();
    
    if (processedData[field]) {
      if (javaType === 'LocalDateTime' || jdbcType.includes('datetime') || jdbcType.includes('timestamp')) {
        // 日期时间字段：转换为 yyyy-MM-dd HH:mm:ss
        processedData[field] = formatDateTime(processedData[field]);
      } else if (javaType === 'LocalDate' || jdbcType.includes('date')) {
        // 日期字段：转换为 yyyy-MM-dd
        processedData[field] = formatDate(processedData[field]);
      }
    }
  });
  
  return processedData;
}

// 字段重要性评分系统
function calculateFieldImportance(column: any): number {
  let score = 0;
  
  // 基础分数
  score += column.listOperationResult ? 100 : 0;
  
  // 字段名称权重（业务意义）
  const fieldName = (column.javaField || column.field || '').toLowerCase();
  const nameWeights = {
    // 标识类字段（高优先级）
    'name': 20, 'title': 20, 'subject': 18, 'displayname': 18,
    'username': 15, 'nickname': 15, 'realname': 15,
    
    // 状态类字段（中高优先级）
    'status': 12, 'state': 12, 'enabled': 10, 'active': 10,
    
    // 描述类字段（中等优先级）
    'description': 8, 'remark': 8, 'comment': 8, 'summary': 8,
    
    // 数值类字段（中等优先级）
    'amount': 10, 'price': 10, 'total': 10, 'count': 8, 'quantity': 8,
    
    // 时间类字段（低优先级，但重要）
    'createtime': 6, 'updatetime': 4, 'modifytime': 4,
    
    // 系统字段（最低优先级）
    'id': 2, 'createby': 2, 'updateby': 2, 'deleted': 1
  };
  
  for (const [key, weight] of Object.entries(nameWeights)) {
    if (fieldName.includes(key)) {
      score += weight;
      break;
    }
  }
  
  // 数据类型权重
  const javaType = column.javaType || '';
  const jdbcType = (column.jdbcType || '').toLowerCase();
  
  if (javaType === 'String' && jdbcType.includes('varchar')) {
    score += fieldName.includes('name') || fieldName.includes('title') ? 8 : 4;
  } else if (javaType === 'Boolean') {
    score += 6;
  } else if (['Integer', 'Long', 'BigDecimal'].includes(javaType)) {
    score += 5;
  } else if (javaType === 'LocalDateTime') {
    score += fieldName.includes('create') ? 3 : 2;
  }
  
  // 字段长度权重
  const columnLength = column.columnSize || 255;
  if (columnLength <= 50) score += 3;
  else if (columnLength <= 100) score += 1;
  else if (columnLength > 500) score -= 2;
  
  // 是否必填
  if (!column.nullable) score += 2;
  
  // 主键特殊处理
  if (column.primaryKey) {
    score += fieldName === 'id' ? 1 : 10;
  }
  
  return score;
}

// 显示字段接口定义
interface DisplayField {
  key: string;
  label: string;
  javaType?: string;
  jdbcType?: string;
  score: number;
  primaryKey?: boolean;
  dictType?: string;
}

// 智能字段选择器
function getViewDisplayFields(mode: ViewMode): DisplayField[] {
  if (!tableMetadata.value?.columns) return [];
  
  // 计算所有字段的重要性得分
  const scoredFields = tableMetadata.value.columns
    .map(col => ({
      ...col,
      score: calculateFieldImportance(col),
      fieldKey: col.javaField || col.field || col.columnName,
      fieldLabel: col.title || col.displayName || col.columnComment || col.columnName
    }))
    .filter(col => col.score > 0)
    .sort((a, b) => b.score - a.score);
  
  // 根据不同模式选择不同数量的字段
  let maxFields: number;
  switch (mode) {
    case ViewMode.LIST:
      maxFields = 3;
      break;
    case ViewMode.CARD:
      maxFields = 6;
      break;
    default:
      maxFields = scoredFields.length;
  }
  
  return scoredFields.slice(0, maxFields).map(col => ({
    key: col.fieldKey,
    label: col.fieldLabel,
    javaType: col.javaType,
    jdbcType: col.jdbcType,
    score: col.score,
    primaryKey: col.primaryKey,
    dictType: col.dictType
  }));
}

// 卡片布局接口
interface CardLayout {
  title: DisplayField | null;
  subtitle: DisplayField | null;
  mainFields: DisplayField[];
  metaFields: DisplayField[];
}

// 卡片字段自适应布局
function getCardFieldLayout(fields: DisplayField[]): CardLayout {
  const layout: CardLayout = {
    title: null,
    subtitle: null,
    mainFields: [],
    metaFields: []
  };
  
  // 选择标题字段（得分最高的非主键字段）
  const titleField = fields.find(f => !f.primaryKey && f.score > 15);
  if (titleField) {
    layout.title = titleField;
    fields = fields.filter(f => f.key !== titleField.key);
  }
  
  // 选择副标题（状态类或描述类字段）
  const subtitleField = fields.find(f => 
    f.key.toLowerCase().includes('status') || 
    f.key.toLowerCase().includes('description') ||
    f.javaType === 'Boolean'
  );
  if (subtitleField) {
    layout.subtitle = subtitleField;
    fields = fields.filter(f => f.key !== subtitleField.key);
  }
  
  // 剩余字段按重要性分为主要字段和次要字段
  layout.mainFields = fields.slice(0, 3);
  layout.metaFields = fields.slice(3);
  
  return layout;
}

// 视图模式相关工具函数
function getViewModeIcon(): string {
  const icons = {
    table: 'mdi:table',
    card: 'mdi:card-outline',
    list: 'mdi:format-list-bulleted'
  };
  return icons[viewMode.value];
}

function switchViewMode(mode: ViewMode) {
  viewMode.value = mode;
  // 保存用户偏好到localStorage
  localStorage.setItem('preferred-view-mode', mode);
}

function handleViewModeChange({ key }: { key: string }) {
  switchViewMode(key as ViewMode);
}

// 格式化字段值显示
function formatFieldValue(value: any, field: DisplayField): string {
  if (!value && value !== 0 && value !== false) return '-';
  
  const javaType = field.javaType || '';
  const jdbcType = (field.jdbcType || '').toLowerCase();
  
  // 日期时间格式化
  if (javaType === 'LocalDateTime' || jdbcType.includes('datetime') || jdbcType.includes('timestamp')) {
    try {
      return new Date(value).toLocaleString('zh-CN');
    } catch {
      return String(value);
    }
  }
  
  // 日期格式化
  if (javaType === 'LocalDate' || jdbcType.includes('date')) {
    try {
      return new Date(value).toLocaleDateString('zh-CN');
    } catch {
      return String(value);
    }
  }
  
  // 布尔值格式化
  if (javaType === 'Boolean' || jdbcType.includes('bit')) {
    return value ? '是' : '否';
  }
  
  // 长文本截断
  if (typeof value === 'string' && value.length > 50) {
    return value.substring(0, 50) + '...';
  }
  
  return String(value);
}

// 计算属性：获取当前模式的显示字段
const currentViewFields = computed(() => getViewDisplayFields(viewMode.value));

// 计算属性：卡片布局
const cardLayout = computed(() => {
  const fields = getViewDisplayFields(ViewMode.CARD);
  return getCardFieldLayout(fields);
});

// 计算属性：主键字段
const primaryKey = computed(() => tableMetadata.value?.primaryKey || 'id');

// 获取卡片标题
function getCardTitle(item: any): string {
  if (cardLayout.value.title) {
    const titleValue = item[cardLayout.value.title.key];
    if (titleValue) return String(titleValue);
  }
  
  // 降级策略：寻找其他可能的标题字段
  const fallbackFields = ['name', 'title', 'subject', 'displayName'];
  for (const fieldName of fallbackFields) {
    for (const col of tableMetadata.value?.columns || []) {
      const key = col.javaField || col.field || '';
      if (key.toLowerCase().includes(fieldName.toLowerCase())) {
        const value = item[key];
        if (value) return String(value);
      }
    }
  }
  
  // 最终降级：使用主键
  const primaryKeyValue = item[primaryKey.value];
  return `${tableMetadata.value?.displayName || tableName.value} #${primaryKeyValue}`;
}

// 处理卡片点击事件
function handleCardClick(item: any) {
  // 可以实现点击卡片查看详情的逻辑
  console.log('Card clicked:', item);
}

// 处理卡片操作菜单
function handleCardAction({ key }: { key: string }) {
  const [action, id] = key.split('-');
  const item = tableData.value.find(row => row[primaryKey.value] == id);
  
  if (!item) return;
  
  switch (action) {
    case 'edit':
      handleEdit(item);
      break;
    case 'delete':
      handleDelete(item);
      break;
  }
}

// 通用API调用处理器
async function executeApiCall(apiCall: () => Promise<any>, successMessage: string, successCallback?: () => void | Promise<void>) {
  try {
    await apiCall();
    message.success(successMessage);
    if (successCallback) await successCallback();
    return true;
  } catch (error) {
    // Magic API 成功响应处理
    if (error?.code === 200 && error?.message === 'success') {
      message.success(successMessage);
      if (successCallback) await successCallback();
      return true;
    }
    throw error;
  }
}

// 新增记录
function handleCreate() {
  if (!tableMetadata.value) {
    message.error('表结构信息未加载');
    return;
  }

  formModalApi.setData({
    title: `新增${tableMetadata.value.displayName || tableMetadata.value.tableName || tableName.value}`,
    metadata: tableMetadata.value,
    tableName: tableName.value,
    dataSourceId: dataSourceId.value,
    isEdit: false,
    onConfirm: async (formData: any) => {
      const realDataSourceId = tableMetadata.value?.table?.dataSourceConfigId ?? dataSourceId.value;
      
      // 处理时间字段格式转换（双重保护）
      const processedFormData = processFormDataTimeFields(formData);
      
      const apiCall = () => useMagicApi.value 
        ? createTableDataMagic(tableName.value, processedFormData)
        : createTableData(tableName.value, processedFormData, realDataSourceId);
      
      const successCallback = async () => {
        refreshTable();
        await formModalApi.close();
      };
      
      try {
        return await executeApiCall(apiCall, '新增成功', successCallback);
      } catch (error) {
        console.error('新增失败:', error);
        message.error('新增失败: ' + (error?.message || error?.msg || '未知错误'));
        return false;
      }
    },
  }).open();
}

// 编辑记录
function handleEdit(row: GenericTableApi.TableData) {
  if (!tableMetadata.value) {
    message.error('表结构信息未加载');
    return;
  }

  formModalApi.setData({
    title: `编辑${tableMetadata.value.displayName || tableMetadata.value.tableName || tableName.value}`,
    metadata: tableMetadata.value,
    tableName: tableName.value,
    dataSourceId: dataSourceId.value,
    isEdit: true,
    record: { ...row },
    onConfirm: async (formData: any) => {
      const primaryKey = tableMetadata.value!.primaryKey;
      formData[primaryKey] = row[primaryKey]; // 确保包含主键ID
      const realDataSourceId = tableMetadata.value?.table?.dataSourceConfigId ?? dataSourceId.value;
      
      // 处理时间字段格式转换（双重保护）
      const processedFormData = processFormDataTimeFields(formData);
      
      const apiCall = () => useMagicApi.value 
        ? updateTableDataMagic(tableName.value, processedFormData)
        : updateTableData(tableName.value, processedFormData, realDataSourceId);
      
      const successCallback = async () => {
        refreshTable();
        await formModalApi.close();
      };
      
      try {
        return await executeApiCall(apiCall, '更新成功', successCallback);
      } catch (error) {
        console.error('更新失败:', error);
        message.error('更新失败: ' + (error?.message || error?.msg || '未知错误'));
        return false;
      }
    },
  }).open();
}

// 删除记录
async function handleDelete(row: GenericTableApi.TableData) {
  if (!tableMetadata.value) return;

  const primaryKey = tableMetadata.value.primaryKey;
  const id = row[primaryKey];
  const realDataSourceId = tableMetadata.value?.table?.dataSourceConfigId ?? dataSourceId.value;
  
  const apiCall = () => useMagicApi.value 
    ? deleteTableDataMagic(tableName.value, id)
    : deleteTableData(tableName.value, id, realDataSourceId);
  
  try {
    await executeApiCall(apiCall, '删除成功', refreshTable);
  } catch (error) {
    console.error('删除失败:', error);
    message.error('删除失败: ' + (error?.message || error?.msg || '未知错误'));
  }
}

// 批量删除
async function handleBatchDelete() {
  const selectedRows = gridApi.grid.getCheckboxRecords();
  if (selectedRows.length === 0) {
    message.warning('请选择要删除的记录');
    return;
  }

  if (!tableMetadata.value) return;

  const primaryKey = tableMetadata.value.primaryKey;
  const ids = selectedRows.map((row) => row[primaryKey]);
  const realDataSourceId = tableMetadata.value?.table?.dataSourceConfigId ?? dataSourceId.value;

  const apiCall = () => useMagicApi.value 
    ? batchDeleteTableDataMagic(tableName.value, ids)
    : batchDeleteTableData(tableName.value, ids, realDataSourceId);
  
  try {
    await executeApiCall(apiCall, `成功删除 ${selectedRows.length} 条记录`, refreshTable);
  } catch (error) {
    console.error('批量删除失败:', error);
    message.error('批量删除失败: ' + (error?.message || error?.msg || '未知错误'));
  }
}

// 导出数据
async function handleExport() {
  const realDataSourceId = tableMetadata.value?.table?.dataSourceConfigId ?? dataSourceId.value;
  
  // 获取当前表格的搜索条件和排序信息
  const currentParams: any = {};
  
  // 获取表格当前的搜索表单数据
  if (gridApi && gridApi.getForm) {
    const formData = gridApi.getForm().getValues();
    Object.assign(currentParams, formData);
  }
  
  // 获取表格当前的排序信息
  if (gridApi && gridApi.getSortColumns) {
    const sortColumns = gridApi.getSortColumns();
    if (sortColumns && sortColumns.length > 0) {
      const sortColumn = sortColumns[0];
      currentParams.sortField = sortColumn.field;
      currentParams.sortOrder = sortColumn.order; // asc 或 desc
    }
  }
  
  try {
    let blobData;
    
    if (useMagicApi.value) {
      blobData = await exportTableDataMagic(tableName.value);
    } else {
      blobData = await exportTableData(tableName.value, currentParams, realDataSourceId);
    }
    
    // 处理文件下载
    if (blobData instanceof Blob) {
      const fileName = `${tableMetadata.value?.displayName || tableName.value}_导出数据_${new Date().toISOString().slice(0, 10)}.xlsx`;
      downloadFileFromBlob({
        source: blobData,
        fileName: fileName
      });
      message.success('导出成功');
    } else {
      console.error('导出响应不是Blob类型:', blobData);
      message.error('导出失败: 响应格式错误');
    }
  } catch (error) {
    // Magic API 成功响应处理
    if (error?.code === 200 && error?.message === 'success') {
      // 对于Magic API，error实际上包含了响应数据
      if (error.data instanceof Blob) {
        const fileName = `${tableMetadata.value?.displayName || tableName.value}_导出数据_${new Date().toISOString().slice(0, 10)}.xlsx`;
        downloadFileFromBlob({
          source: error.data,
          fileName: fileName
        });
        message.success('导出成功');
        return;
      }
    }
    
    console.error('导出失败:', error);
    message.error('导出失败: ' + (error?.message || error?.msg || '未知错误'));
  }
}

// 刷新表格数据
function refreshTable() {
  gridApi.query();
}

// 搜索相关参数
const searchParams = ref<any>({});

// Popover搜索表单相关
const popoverSearchFormApi = ref<any>(null);
const popoverSearchFormRules = ref<any[]>([]);
const searchPopoverVisible = ref(false);


// 搜索表单提交
function handleSearchSubmit(formData: any) {
  // 过滤空值
  const filteredParams = Object.keys(formData).reduce((acc, key) => {
    const value = formData[key];
    if (value !== undefined && value !== null && value !== '') {
      acc[key] = value;
    }
    return acc;
  }, {} as any);
  
  searchParams.value = filteredParams;
  gridApi.query();
}


// Popover搜索表单提交
function handlePopoverSearchSubmit() {
  if (popoverSearchFormApi.value) {
    const formData = popoverSearchFormApi.value.formData();
    handleSearchSubmit(formData);
    searchPopoverVisible.value = false; // 提交后关闭弹窗
  }
}

// Popover搜索表单重置
function handlePopoverSearchReset() {
  if (popoverSearchFormApi.value) {
    popoverSearchFormApi.value.resetFields();
  }
  searchParams.value = {};
  gridApi.query();
  searchPopoverVisible.value = false; // 重置后关闭弹窗
}


// 处理搜索树选择
function handleTreeSelect(selectedKeysValue: string[]) {
  selectedKeys.value = selectedKeysValue;
  // 根据选择的节点过滤数据，暂时只刷新表格
  refreshTable();
}

// 处理行选择变化
function handleRowCheckboxChange({ records }: { records: GenericTableApi.TableData[] }) {
  if (!tableMetadata.value) return;
  const primaryKey = tableMetadata.value.primaryKey;
  checkedIds.value = records.map((item) => item[primaryKey]);
}

// 根据htmlType获取form-create组件类型（复用表单构建器的逻辑）
function getFormComponentTypeByHtmlType(column: any) {
  const htmlType = column.htmlType || 'input';
  
  switch (htmlType) {
    case 'input':
      return { type: 'input', dragTag: 'input' };
    case 'textarea':
      return { type: 'input', dragTag: 'textarea', props: { type: 'textarea' } };
    case 'select':
      // 如果是字典字段，加载字典选项
      const selectOptions = isDictField(column) ? getDictSelectOptions(column.dictType) : [];
      return { type: 'select', dragTag: 'select', options: selectOptions };
    case 'radio':
      // 如果是字典字段，加载字典选项
      const radioOptions = isDictField(column) ? getDictSelectOptions(column.dictType) : [];
      return { type: 'radio', dragTag: 'radio', options: radioOptions };
    case 'checkbox':
      // 如果是字典字段，加载字典选项
      const checkboxOptions = isDictField(column) ? getDictSelectOptions(column.dictType) : [];
      return { type: 'checkbox', dragTag: 'checkbox', options: checkboxOptions };
    case 'datetime':
      return { type: 'DatePicker', dragTag: 'DatePicker', props: { showTime: true, format: 'YYYY-MM-DD HH:mm:ss' } };
    case 'date':
      return { type: 'DatePicker', dragTag: 'DatePicker', props: { format: 'YYYY-MM-DD' } };
    default:
      return { type: 'input', dragTag: 'input' };
  }
}


// 生成搜索表单的form-create规则（基于表单构建器逻辑）
function generateSearchFormRules(columns: any[]) {
  const rules: any[] = [];
  
  // 过滤出可搜索的字段
  const searchableColumns = columns.filter(col => col.listOperation === true);
  
  searchableColumns.forEach((col) => {
    const fieldName = col.javaField || col.columnName;
    const fieldTitle = col.title || col.columnComment || fieldName;
    const componentType = getFormComponentTypeByHtmlType(col);
    
    // 生成唯一的ID和name
    const uniqueId = `search_${fieldName}_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`;
    const fcId = `id_${uniqueId}`;
    const refName = `ref_${uniqueId}`;
    
    const rule: any = {
      type: componentType.type,
      field: fieldName,
      title: fieldTitle,
      info: '',
      $required: false, // 搜索字段不要求必填
      _fc_id: fcId,
      name: refName,
      display: true,
      hidden: false,
      _fc_drag_tag: componentType.dragTag,
      props: {
        placeholder: isDictField(col) ? `请选择${fieldTitle}` : `请输入${fieldTitle}`,
        clearable: true, // 搜索字段支持清空
        allowClear: true, // 允许清空
        style: { width: '200px' }, // 统一字段宽度
        ...componentType.props,
      },
      wrap: {
        labelCol: { span: 0 },
        wrapperCol: { span: 24 },
        style: {
          display: 'inline-block',
          width: '250px',
          marginRight: '16px',
          marginBottom: '16px'
        }
      }
    };
    
    // 添加选项（如果是选择类组件）
    if (componentType.options) {
      // 如果是字典字段，在搜索表单中添加"全部"选项
      if (isDictField(col) && componentType.type === 'select') {
        rule.options = [
          { label: '全部', value: '' },
          ...componentType.options
        ];
      } else {
        rule.options = componentType.options;
      }
    }
    
    rules.push(rule);
  });
  
  return rules;
}


// 生成紧凑的Popover搜索表单规则（2列布局）
function generateCompactSearchFormRules(columns: any[]) {
  const rules: any[] = [];
  
  // 过滤出可搜索的字段
  const searchableColumns = columns.filter(col => col.listOperation === true);
  
  searchableColumns.forEach((col) => {
    const fieldName = col.javaField || col.columnName;
    const fieldTitle = col.title || col.columnComment || fieldName;
    const componentType = getFormComponentTypeByHtmlType(col);
    
    // 生成唯一的ID和name
    const uniqueId = `popover_${fieldName}_${Date.now()}_${Math.random().toString(36).substr(2, 9)}`;
    const fcId = `id_${uniqueId}`;
    const refName = `ref_${uniqueId}`;
    
    const rule: any = {
      type: componentType.type,
      field: fieldName,
      title: fieldTitle,
      info: '',
      $required: false, // 搜索字段不要求必填
      _fc_id: fcId,
      name: refName,
      display: true,
      hidden: false,
      _fc_drag_tag: componentType.dragTag,
      props: {
        placeholder: isDictField(col) ? `请选择${fieldTitle}` : `请输入${fieldTitle}`,
        clearable: true, // 搜索字段支持清空
        allowClear: true, // 允许清空
        size: 'small', // 紧凑尺寸
        style: { width: '100%' }, // 填满容器宽度
        ...componentType.props,
      },
      col: {
        span: 12, // 2列布局，每列占12格
      }
    };
    
    // 添加选项（如果是选择类组件）
    if (componentType.options) {
      // 如果是字典字段，在搜索表单中添加"全部"选项
      if (isDictField(col) && componentType.type === 'select') {
        rule.options = [
          { label: '全部', value: '' },
          ...componentType.options
        ];
      } else {
        rule.options = componentType.options;
      }
    }
    
    rules.push(rule);
  });
  
  return rules;
}

// VXE表格搜索表单配置（保留但可能不用）
function useGridFormSchema() {
  return [];
}

// 表格配置
const [Grid, gridApi] = useVbenVxeGrid({
  gridOptions: {
    columns: useGridColumns(),
    height: 'auto',
    keepSource: true,
    proxyConfig: {
      ajax: {
        query: async ({ page }, formValues) => {
          try {
            const realTableName = tableMetadata.value?.tableName || tableName.value;
            if (!realTableName) {
              throw new Error('表名不存在');
            }
            
            const realDataSourceId = tableMetadata.value?.table?.dataSourceConfigId ?? dataSourceId.value;
            
            let response;
            if (useMagicApi.value) {
              // Magic API参数：page/size放URL，搜索条件作为JSON body
              const searchConditions = {
                ...formValues, // VXE表格内置搜索表单的参数  
                ...searchParams.value, // form-create搜索表单的参数
              };
              
              const magicParams = {
                page: page.currentPage,
                size: page.pageSize,
                // 搜索条件直接作为body传递，不再展开
                ...searchConditions
              };
              
              response = await getTableDataMagic(realTableName, magicParams);
            } else {
              // 原有API参数：需要dataSourceId
              const params: any = {
                pageNo: page.currentPage,
                pageSize: page.pageSize,
                ...formValues, // VXE表格内置搜索表单的参数  
                ...searchParams.value, // form-create搜索表单的参数
              };
              
              // 如果有数据源ID就传递，后端查询接口也需要dataSourceId参数
              if (realDataSourceId !== undefined && realDataSourceId !== null) {
                params.dataSourceId = realDataSourceId;
              }
              
              response = await getTableData(realTableName, params);
            }
            
            // 同步数据到统一数据源（供卡片和列表模式使用）
            if (response && (response.list || response.data)) {
              tableData.value = response.list || response.data || [];
            }
            
            return response;
          } catch (error) {
            // Magic API 成功响应被拦截器误判为错误时的处理
            if (error?.code === 200 && error?.message === 'success') {
              return error.data;
            }
            // 真正的错误重新抛出
            throw error;
          }
        },
      },
    },
    rowConfig: {
      keyField: 'id',
      isHover: true,
    },
    toolbarConfig: {
      refresh: true,
      search: false, // 禁用内置搜索按钮
      custom: true, // 启用自定义工具栏按钮
    },
  },
  gridEvents: {
    checkboxAll: handleRowCheckboxChange,
    checkboxChange: handleRowCheckboxChange,
  },
} as any);


// 组件初始化
onMounted(async () => {
  // 恢复用户的视图模式偏好
  const savedViewMode = localStorage.getItem('preferred-view-mode');
  if (savedViewMode && Object.values(ViewMode).includes(savedViewMode as ViewMode)) {
    viewMode.value = savedViewMode as ViewMode;
  }
  
  await loadTableMetadata();
  // 表结构加载完成后，VXE表格的proxyConfig会自动加载数据
});
</script>

<template>
  <Page auto-content-height>
    
    <div class="flex h-full w-full">
      <!-- 左侧搜索树 -->
      <div class="w-64 min-w-64 border-r pr-4">
        <a-card title="搜索条件" size="small" class="h-full">
          <a-tree
            :tree-data="searchTreeData"
            :selected-keys="selectedKeys"
            @select="handleTreeSelect"
            class="mt-2"
          />
        </a-card>
      </div>
      
      <!-- 右侧表格 -->
      <div class="flex-1 min-w-0 pl-4">
        
        <!-- 表格模式 -->
        <Grid 
          v-if="viewMode === 'table'"
          :table-title="tableMetadata?.displayName || tableMetadata?.tableName || '通用表格'"
        >
          <template #toolbar-actions>
            <TableAction
              :actions="[
                {
                  label: '新增',
                  type: 'primary',
                  icon: ACTION_ICON.ADD,
                  onClick: handleCreate,
                },
                {
                  label: '导出',
                  type: 'primary',
                  icon: ACTION_ICON.DOWNLOAD,
                  onClick: handleExport,
                },
                {
                  label: '批量删除',
                  type: 'primary',
                  danger: true,
                  disabled: isEmpty(checkedIds),
                  icon: ACTION_ICON.DELETE,
                  onClick: handleBatchDelete,
                },
              ]"
            />
          </template>
          
          <template #toolbar-tools>
            <!-- 搜索按钮 -->
            <Popover 
              v-model:open="searchPopoverVisible" 
              title="搜索条件" 
              trigger="click"
              placement="bottomRight"
            >
              <template #content>
                <div style="width: 700px; padding: 16px;">
                  <form-create
                    v-if="popoverSearchFormRules.length > 0"
                    v-model:api="popoverSearchFormApi"
                    :rule="popoverSearchFormRules"
                    :option="{
                      form: { 
                        layout: 'horizontal',
                        colon: true,
                        size: 'small',
                        labelCol: { span: 6 },
                        wrapperCol: { span: 18 }
                      },
                      row: {
                        gutter: [16, 8]
                      },
                      wrap: { 
                        labelCol: { span: 6 },
                        wrapperCol: { span: 18 }
                      },
                      submitBtn: false,
                      resetBtn: false
                    }"
                  />
                  <div v-else>
                    <p>暂无可搜索字段</p>
                  </div>
                  <div class="flex justify-end gap-2 mt-4">
                    <a-button @click="handlePopoverSearchReset">重置</a-button>
                    <a-button type="primary" @click="handlePopoverSearchSubmit">搜索</a-button>
                    <a-button @click="searchPopoverVisible = false">取消</a-button>
                  </div>
                </div>
              </template>
              <Button
                shape="circle"
                size="default"
                @click="searchPopoverVisible = !searchPopoverVisible"
              >
                <template #icon>
                  <IconifyIcon :icon="ACTION_ICON.SEARCH" />
                </template>
              </Button>
            </Popover>
            
            <!-- 视图模式切换按钮 -->
            <Dropdown @click="handleViewModeChange">
              <Button
                shape="circle"
                size="default"
                :title="`当前视图：${viewMode === 'table' ? '表格' : viewMode === 'card' ? '卡片' : '列表'}`"
              >
                <template #icon>
                  <IconifyIcon :icon="getViewModeIcon()" />
                </template>
              </Button>
              <template #overlay>
                <Menu @click="handleViewModeChange">
                  <MenuItem key="table" :class="{ 'ant-menu-item-selected': viewMode === 'table' }">
                    <IconifyIcon icon="mdi:table" class="mr-2" />
                    表格视图
                  </MenuItem>
                  <MenuItem key="card" :class="{ 'ant-menu-item-selected': viewMode === 'card' }">
                    <IconifyIcon icon="mdi:card-outline" class="mr-2" />
                    卡片视图
                  </MenuItem>
                  <MenuItem key="list" :class="{ 'ant-menu-item-selected': viewMode === 'list' }">
                    <IconifyIcon icon="mdi:format-list-bulleted" class="mr-2" />
                    列表视图
                  </MenuItem>
                </Menu>
              </template>
            </Dropdown>
          </template>
          <template #actions="{ row }">
            <TableAction
              :actions="[
                {
                  label: '编辑',
                  type: 'link',
                  icon: ACTION_ICON.EDIT,
                  onClick: handleEdit.bind(null, row),
                },
                {
                  label: '删除',
                  type: 'link',
                  danger: true,
                  icon: ACTION_ICON.DELETE,
                  popConfirm: {
                    title: '确认删除吗？',
                    confirm: handleDelete.bind(null, row),
                  },
                },
              ]"
            />
          </template>
        </Grid>

        <!-- 卡片模式 -->
        <div v-else-if="viewMode === 'card'" class="space-y-4">
          <!-- 卡片模式工具栏 -->
          <div class="flex justify-between items-center">
            <h3 class="text-lg font-semibold">
              {{ tableMetadata?.displayName || tableMetadata?.tableName || '通用表格' }} ({{ tableData.length }} 条记录)
            </h3>
            <div class="flex gap-2">
              <!-- 搜索按钮 -->
              <Popover 
                v-model:open="searchPopoverVisible" 
                title="搜索条件" 
                trigger="click"
                placement="bottomLeft"
              >
                <template #content>
                  <div style="width: 700px; padding: 16px;">
                    <form-create
                      v-if="popoverSearchFormRules.length > 0"
                      v-model:api="popoverSearchFormApi"
                      :rule="popoverSearchFormRules"
                      :option="{
                        form: { 
                          layout: 'horizontal',
                          colon: true,
                          size: 'small',
                          labelCol: { span: 6 },
                          wrapperCol: { span: 18 }
                        },
                        row: {
                          gutter: [16, 8]
                        },
                        wrap: { 
                          labelCol: { span: 6 },
                          wrapperCol: { span: 18 }
                        },
                        submitBtn: false,
                        resetBtn: false
                      }"
                    />
                    <div v-else>
                      <p>暂无可搜索字段</p>
                    </div>
                    <div class="flex justify-end gap-2 mt-4">
                      <a-button @click="handlePopoverSearchReset">重置</a-button>
                      <a-button type="primary" @click="handlePopoverSearchSubmit">搜索</a-button>
                      <a-button @click="searchPopoverVisible = false">取消</a-button>
                    </div>
                  </div>
                </template>
                <Button size="small">
                  <IconifyIcon :icon="ACTION_ICON.SEARCH" class="mr-2" />
                  搜索
                </Button>
              </Popover>
              
              <!-- 视图切换按钮 -->
              <Dropdown @click="handleViewModeChange">
                <Button size="small">
                  <IconifyIcon :icon="getViewModeIcon()" class="mr-2" />
                  视图
                </Button>
                <template #overlay>
                  <Menu @click="handleViewModeChange">
                    <MenuItem key="table">
                      <IconifyIcon icon="mdi:table" class="mr-2" />
                      表格视图
                    </MenuItem>
                    <MenuItem key="card" class="ant-menu-item-selected">
                      <IconifyIcon icon="mdi:card-outline" class="mr-2" />
                      卡片视图
                    </MenuItem>
                    <MenuItem key="list">
                      <IconifyIcon icon="mdi:format-list-bulleted" class="mr-2" />
                      列表视图
                    </MenuItem>
                  </Menu>
                </template>
              </Dropdown>
              
              <!-- 操作按钮 -->
              <Button type="primary" @click="handleCreate">
                <IconifyIcon :icon="ACTION_ICON.ADD" class="mr-2" />
                新增
              </Button>
              <Button @click="handleExport">
                <IconifyIcon :icon="ACTION_ICON.DOWNLOAD" class="mr-2" />
                导出
              </Button>
            </div>
          </div>
          
          <!-- 卡片容器 -->
          <div class="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 xl:grid-cols-4 gap-4 max-h-[calc(100vh-300px)] overflow-y-auto">
            <Card 
              v-for="item in tableData" 
              :key="item[primaryKey]"
              class="hover:shadow-lg transition-all duration-300 cursor-pointer transform hover:-translate-y-1"
              @click="handleCardClick(item)"
            >
              <template #title>
                <div class="truncate text-sm font-medium">
                  {{ getCardTitle(item) }}
                </div>
              </template>
              
              <template #extra>
                <Dropdown @click.stop>
                  <Button type="text" size="small">
                    <IconifyIcon icon="mdi:dots-vertical" />
                  </Button>
                  <template #overlay>
                    <Menu @click="handleCardAction">
                      <MenuItem :key="`edit-${item[primaryKey]}`">
                        <IconifyIcon icon="mdi:pencil" class="mr-2" />
                        编辑
                      </MenuItem>
                      <MenuItem :key="`delete-${item[primaryKey]}`" class="text-red-500">
                        <IconifyIcon icon="mdi:delete" class="mr-2" />
                        删除
                      </MenuItem>
                    </Menu>
                  </template>
                </Dropdown>
              </template>
              
              <!-- 卡片内容 -->
              <div class="space-y-3">
                <!-- 副标题 -->
                <div v-if="cardLayout.subtitle" class="text-gray-600 text-sm">
                  {{ formatFieldValue(item[cardLayout.subtitle.key], cardLayout.subtitle) }}
                </div>
                
                <!-- 主要字段 -->
                <div class="space-y-2">
                  <div 
                    v-for="field in cardLayout.mainFields" 
                    :key="field.key"
                    class="flex justify-between items-start"
                  >
                    <span class="text-gray-500 text-xs truncate mr-2 flex-shrink-0">{{ field.label }}:</span>
                    <span class="text-gray-900 text-xs font-medium truncate text-right flex-shrink">
                      {{ formatFieldValue(item[field.key], field) }}
                    </span>
                  </div>
                </div>
                
                <!-- 次要字段（可折叠） -->
                <Collapse v-if="cardLayout.metaFields.length > 0" size="small" ghost>
                  <CollapsePanel key="more" header="更多信息">
                    <div class="space-y-1">
                      <div 
                        v-for="field in cardLayout.metaFields" 
                        :key="field.key"
                        class="flex justify-between items-start text-xs"
                      >
                        <span class="text-gray-400 truncate mr-2 flex-shrink-0">{{ field.label }}:</span>
                        <span class="text-gray-600 truncate text-right flex-shrink">
                          {{ formatFieldValue(item[field.key], field) }}
                        </span>
                      </div>
                    </div>
                  </CollapsePanel>
                </Collapse>
              </div>
            </Card>
            
            <!-- 空状态 -->
            <div v-if="tableData.length === 0" class="col-span-full flex flex-col items-center justify-center py-12 text-gray-400">
              <IconifyIcon icon="mdi:database-off" class="text-6xl mb-4" />
              <p>暂无数据</p>
            </div>
          </div>
        </div>

        <!-- 列表模式 -->
        <div v-else-if="viewMode === 'list'" class="space-y-4">
          <!-- 列表模式工具栏 -->
          <div class="flex justify-between items-center">
            <h3 class="text-lg font-semibold">
              {{ tableMetadata?.displayName || tableMetadata?.tableName || '通用表格' }} ({{ tableData.length }} 条记录)
            </h3>
            <div class="flex gap-2">
              <!-- 搜索按钮 -->
              <Popover 
                v-model:open="searchPopoverVisible" 
                title="搜索条件" 
                trigger="click"
                placement="bottomLeft"
              >
                <template #content>
                  <div style="width: 700px; padding: 16px;">
                    <form-create
                      v-if="popoverSearchFormRules.length > 0"
                      v-model:api="popoverSearchFormApi"
                      :rule="popoverSearchFormRules"
                      :option="{
                        form: { 
                          layout: 'horizontal',
                          colon: true,
                          size: 'small',
                          labelCol: { span: 6 },
                          wrapperCol: { span: 18 }
                        },
                        row: {
                          gutter: [16, 8]
                        },
                        wrap: { 
                          labelCol: { span: 6 },
                          wrapperCol: { span: 18 }
                        },
                        submitBtn: false,
                        resetBtn: false
                      }"
                    />
                    <div v-else>
                      <p>暂无可搜索字段</p>
                    </div>
                    <div class="flex justify-end gap-2 mt-4">
                      <a-button @click="handlePopoverSearchReset">重置</a-button>
                      <a-button type="primary" @click="handlePopoverSearchSubmit">搜索</a-button>
                      <a-button @click="searchPopoverVisible = false">取消</a-button>
                    </div>
                  </div>
                </template>
                <Button size="small">
                  <IconifyIcon :icon="ACTION_ICON.SEARCH" class="mr-2" />
                  搜索
                </Button>
              </Popover>
              
              <!-- 视图切换按钮 -->
              <Dropdown @click="handleViewModeChange">
                <Button size="small">
                  <IconifyIcon :icon="getViewModeIcon()" class="mr-2" />
                  视图
                </Button>
                <template #overlay>
                  <Menu @click="handleViewModeChange">
                    <MenuItem key="table">
                      <IconifyIcon icon="mdi:table" class="mr-2" />
                      表格视图
                    </MenuItem>
                    <MenuItem key="card">
                      <IconifyIcon icon="mdi:card-outline" class="mr-2" />
                      卡片视图
                    </MenuItem>
                    <MenuItem key="list" class="ant-menu-item-selected">
                      <IconifyIcon icon="mdi:format-list-bulleted" class="mr-2" />
                      列表视图
                    </MenuItem>
                  </Menu>
                </template>
              </Dropdown>
              
              <!-- 操作按钮 -->
              <Button type="primary" @click="handleCreate">
                <IconifyIcon :icon="ACTION_ICON.ADD" class="mr-2" />
                新增
              </Button>
              <Button @click="handleExport">
                <IconifyIcon :icon="ACTION_ICON.DOWNLOAD" class="mr-2" />
                导出
              </Button>
            </div>
          </div>
          
          <!-- 列表容器 -->
          <div class="bg-white rounded-lg shadow max-h-[calc(100vh-300px)] overflow-y-auto">
            <List :dataSource="tableData">
              <template #renderItem="{ item }">
                <ListItem class="hover:bg-gray-50 cursor-pointer" @click="handleCardClick(item)">
                  <ListItemMeta>
                    <template #title>
                      <div class="font-medium text-gray-900">
                        {{ getCardTitle(item) }}
                      </div>
                    </template>
                    <template #description>
                      <div class="flex flex-wrap gap-4 text-sm text-gray-600">
                        <span v-for="field in getViewDisplayFields(ViewMode.LIST)" :key="field.key">
                          <strong class="text-gray-700">{{ field.label }}:</strong> 
                          {{ formatFieldValue(item[field.key], field) }}
                        </span>
                      </div>
                    </template>
                  </ListItemMeta>
                  <template #actions>
                    <Button type="link" size="small" @click.stop="handleEdit(item)">
                      <IconifyIcon :icon="ACTION_ICON.EDIT" class="mr-1" />
                      编辑
                    </Button>
                    <Button type="link" size="small" danger @click.stop="handleDelete(item)">
                      <IconifyIcon :icon="ACTION_ICON.DELETE" class="mr-1" />
                      删除
                    </Button>
                  </template>
                </ListItem>
              </template>
              
              <!-- 空状态 -->
              <template #empty>
                <div class="flex flex-col items-center justify-center py-12 text-gray-400">
                  <IconifyIcon icon="mdi:database-off" class="text-6xl mb-4" />
                  <p>暂无数据</p>
                </div>
              </template>
            </List>
          </div>
        </div>
      </div>
    </div>

    <!-- 表单弹窗 -->
    <FormModal ref="formModalRef" />
  </Page>
</template>
